﻿namespace KeRui.Common
{
    using System;
    using System.Diagnostics;
    using System.IO;
    using System.Runtime.InteropServices;
    using System.Text.RegularExpressions;

    public class Winrar
    {
        private string password;
        private string winrarExe;

        public Winrar(string directoryOfWinrarExe)
        {
            directoryOfWinrarExe = CheckDirectoryName(directoryOfWinrarExe);
            this.winrarExe = directoryOfWinrarExe + "Winrar.exe";
            this.password = null;
        }

        public Winrar(string directoryOfWinrarExe, string password)
        {
            directoryOfWinrarExe = CheckDirectoryName(directoryOfWinrarExe);
            this.winrarExe = directoryOfWinrarExe + "Winrar.exe";
            this.password = CheckPassword(password);
        }

        private static string CheckDirectoryName(string directoryName)
        {
            if (directoryName == null)
            {
                throw new Exception("目录名不可以为null。");
            }
            Regex regex = new Regex(@"^[a-zA-Z]:[^\n]*\\$");
            if (!regex.IsMatch(directoryName))
            {
                throw new Exception(@"目录名称请用绝对路径，须以“\”结束。如：C:\Windows\。");
            }
            return directoryName;
        }

        private static void CheckFiles(string[] files)
        {
            Regex regex = new Regex(@"[a-zA-Z]:\\.+\..+");
            foreach (string str in files)
            {
                if (str == null)
                {
                    throw new Exception("文件名不可以为null。");
                }
                if (!regex.IsMatch(str))
                {
                    throw new Exception(@"文件名称请用绝对路径，并注意格式。如：C:\Windows\aa.txt");
                }
            }
        }

        private static string CheckPassword(string password)
        {
            if (password == null)
            {
                throw new Exception("密码不可以为null。如不要密码，请用另一无password参数的构造函数。");
            }
            Regex regex = new Regex(@"^\w+$");
            if (!regex.IsMatch(password))
            {
                throw new Exception("密码请用字母，数字，下画线。");
            }
            return password;
        }

        private static string CheckRarFile(string rarFile)
        {
            if (rarFile == null)
            {
                throw new Exception("文件名不可以为null。");
            }
            Regex regex = new Regex(@"^[a-zA-Z]:\\.+\.(?:rar)|(?:zip)$");
            if (!regex.IsMatch(rarFile))
            {
                throw new Exception(@"文件名称请用绝对路径，须以“扩展名.rar”结束。如：C:\Windows\aa.rar");
            }
            return rarFile;
        }

        public void Compress(string rarFileToSave, bool deleteSourceFiles, params string[] filesToCompress)
        {
            string str;
            rarFileToSave = CheckRarFile(rarFileToSave);
            if (File.Exists(rarFileToSave))
            {
                File.Delete(rarFileToSave);
            }
            CheckFiles(filesToCompress);
            this.CreateLstFile(filesToCompress, out str);
            Process process = new Process();
            process.StartInfo.FileName = this.winrarExe;
            string str2 = "a -ep1 -r -o+";
            if (this.password != null)
            {
                str2 = str2 + " -p" + this.password;
            }
            string str4 = str2;
            str2 = str4 + " " + rarFileToSave + " @" + str;
            process.StartInfo.Arguments = str2;
            process.StartInfo.WindowStyle = ProcessWindowStyle.Hidden;
            process.Start();
            while (!process.HasExited)
            {
            }
            process.WaitForExit();
            if (deleteSourceFiles)
            {
                foreach (string str3 in filesToCompress)
                {
                    File.Delete(str3);
                }
            }
            File.Delete(str);
        }

        public void Compress(string directoryToCompress, string rarFileToSave, bool deleteDirectoryToCompress)
        {
            directoryToCompress = CheckDirectoryName(directoryToCompress);
            rarFileToSave = CheckRarFile(rarFileToSave);
            if (File.Exists(rarFileToSave))
            {
                File.Delete(rarFileToSave);
            }
            Process process = new Process();
            process.StartInfo.FileName = this.winrarExe;
            string str = "a -ep1 -r -o+ -inul -y";
            if (this.password != null)
            {
                str = str + " -p" + this.password;
            }
            string str2 = str;
            str = str2 + " " + rarFileToSave + " " + directoryToCompress;
            process.StartInfo.Arguments = str;
            process.StartInfo.WindowStyle = ProcessWindowStyle.Hidden;
            process.Start();
            while (!process.HasExited)
            {
            }
            process.WaitForExit();
            if (deleteDirectoryToCompress)
            {
                Directory.Delete(directoryToCompress, true);
            }
        }

        private void CreateLstFile(string[] filesToCompress, out string lstFile)
        {
            string str = this.winrarExe.Substring(0, this.winrarExe.LastIndexOf("/") + 1);
            string str2 = DateTime.Now.ToString("yyyyMMddHHmmss") + ".lst";
            lstFile = str + str2;
            StreamWriter writer = new StreamWriter(str + str2, false);
            foreach (string str3 in filesToCompress)
            {
                writer.WriteLine(str3);
            }
            writer.Close();
        }

        public void Decompress(string rarFileToDecompress, string directoryToSave, bool deleteRarFile)
        {
            directoryToSave = CheckDirectoryName(directoryToSave);
            rarFileToDecompress = CheckRarFile(rarFileToDecompress);
            Process process = new Process();
            process.StartInfo.FileName = this.winrarExe;
            string str = "x -inul -y -o+";
            if (this.password != null)
            {
                str = str + " -p" + this.password;
            }
            string str2 = str;
            str = str2 + " " + rarFileToDecompress + " " + directoryToSave;
            process.StartInfo.Arguments = str;
            process.StartInfo.WindowStyle = ProcessWindowStyle.Hidden;
            process.Start();
            while (!process.HasExited)
            {
            }
            process.WaitForExit();
            if (deleteRarFile)
            {
                File.Delete(rarFileToDecompress);
            }
        }
    }
}

